using UnityEngine;
using System.Collections.Generic;
using System.IO;
using System.Text.RegularExpressions;
using System.Text;

/// <summary>
/// 单词结构体，包含英文、中文、音标和不完整形式
/// </summary>
[System.Serializable]
public struct Word
{
    public string english;    // 英文单词
    public string chinese;    // 中文意思
    public string phonetic;   // 音标
    public string incomplete; // 不完整形式（如 _ppl_）
    public string answer;     // 正确答案（缺失的字母）
    public List<string> parts; // Excel中拆分的各部分
    public List<string> phoneticParts; // 对应的音标分段
}

/// <summary>
/// 单词数据库类，负责加载和提供单词
/// </summary>
public class WordDatabase : MonoBehaviour
{
    // 单例实例
    public static WordDatabase Instance { get; private set; }
    
    // 单词列表
    [SerializeField]
    private List<Word> words = new List<Word>();
    
    // 单词数据文件路径
    private string dataPath;
    
    // 已使用的单词索引，避免重复
    private List<int> usedWordIndices = new List<int>();
    
    // 单词生成难度设置
    [Range(0f, 1f)]
    public float difficulty = 0.5f; // 0=简单，1=困难
    
    private void Awake()
    {
        // 单例设置
        if (Instance != null && Instance != this)
        {
            Destroy(gameObject);
            return;
        }
        Instance = this;
        
        // 确保在场景切换时不销毁
        DontDestroyOnLoad(gameObject);
        
        // 设置数据文件路径
        dataPath = Path.Combine(Application.streamingAssetsPath, "words.txt");
        
        // 加载单词数据
        LoadWords();
    }
    
    private void Start()
    {
        // 检查ExcelFileImporter中是否有导入的单词数据
        CheckForImportedWords();
        
        // 强制重新处理所有单词的音标分段
        ReprocessAllPhoneticParts();
        
        // 延迟再次检查，以防ExcelFileImporter的自动导入有延迟
        StartCoroutine(DelayedCheckForImportedWords());
    }
    
    /// <summary>
    /// 延迟检查导入的单词数据
    /// </summary>
    private System.Collections.IEnumerator DelayedCheckForImportedWords()
    {
        // 等待1秒，确保ExcelFileImporter有足够时间完成自动导入
        yield return new WaitForSeconds(1.0f);
        
        // 再次检查导入的单词数据
        if (ExcelFileImporter.HasNewImportedWords && ExcelFileImporter.ImportedWords.Count > 0)
        {
            Debug.Log($"延迟检查发现从Excel导入的 {ExcelFileImporter.ImportedWords.Count} 个单词，正在加载...");
            
            // 设置单词列表
            SetWordList(ExcelFileImporter.ImportedWords);
            
            // 重置标记，避免重复加载
            ExcelFileImporter.HasNewImportedWords = false;
            
            // 再次处理音标分段
            ReprocessAllPhoneticParts();
            
            Debug.Log("延迟加载的Excel导入单词已成功添加到WordDatabase");
        }
    }
    
    /// <summary>
    /// 检查并加载从ExcelFileImporter导入的单词数据
    /// </summary>
    public void CheckForImportedWords()
    {
        // 检查ExcelFileImporter是否有新导入的单词
        if (ExcelFileImporter.HasNewImportedWords && ExcelFileImporter.ImportedWords.Count > 0)
        {
            Debug.Log($"在WordDatabase中发现从Excel导入的 {ExcelFileImporter.ImportedWords.Count} 个单词，正在加载...");
            
            // 设置单词列表
            SetWordList(ExcelFileImporter.ImportedWords);
            
            // 重置标记，避免重复加载
            ExcelFileImporter.HasNewImportedWords = false;
            
            Debug.Log("Excel导入的单词已成功加载到WordDatabase");
        }
    }
    
    /// <summary>
    /// 加载单词数据
    /// </summary>
    private void LoadWords()
    {
        // 清空当前列表
        words.Clear();
        
        // 从文件加载单词
        if (File.Exists(dataPath))
        {
            string[] lines = File.ReadAllLines(dataPath);
            foreach (string line in lines)
            {
                if (string.IsNullOrWhiteSpace(line)) continue;
                
                string[] parts = line.Split('|');
                if (parts.Length >= 2)
                {
                    Word word = new Word
                    {
                        english = parts[0].Trim(),
                        chinese = parts[1].Trim(),
                        incomplete = GenerateIncompleteWord(parts[0].Trim()).incomplete,
                        answer = GenerateIncompleteWord(parts[0].Trim()).answer
                    };
                    words.Add(word);
                }
            }
        }
    }
    
    /// <summary>
    /// 生成单词的不完整形式，并返回包含不完整单词和答案的元组
    /// </summary>
    private (string incomplete, string answer) GenerateIncompleteWord(string english)
    {
        if (string.IsNullOrEmpty(english) || english.Length <= 2)
            return (english, "");
            
        // 计算要隐藏的字母数量，基于难度设置
        int letterCount = english.Length;
        int hideCount = Mathf.RoundToInt(letterCount * (0.3f + difficulty * 0.4f)); // 30%-70%的字母被隐藏
        hideCount = Mathf.Clamp(hideCount, 1, letterCount - 1); // 至少保留一个字母
        
        // 创建一个标记数组表示每个位置是否隐藏
        bool[] hidePositions = new bool[letterCount];
        
        // 随机选择要隐藏的位置
        for (int i = 0; i < hideCount; i++)
        {
            int position;
            int attempts = 0;
            
            // 尝试找到一个未被标记的位置
            do
            {
                position = Random.Range(0, letterCount);
                attempts++;
                
                // 防止无限循环
                if (attempts > 100)
                    break;
            }
            while (hidePositions[position]);
            
            hidePositions[position] = true;
        }
        
        // 构建不完整的单词
        char[] incompleteChars = english.ToCharArray();
        string answer = "";
        
        for (int i = 0; i < letterCount; i++)
        {
            if (hidePositions[i])
            {
                answer += english[i];
                incompleteChars[i] = '_';
            }
        }
        
        return (new string(incompleteChars), answer);
    }
    
    /// <summary>
    /// 获取一个随机单词
    /// </summary>
    public Word GetRandomWord()
    {
        if (words.Count == 0)
            return new Word(); // 返回空单词
            
        // 如果已经用完所有单词，重置记录
        if (usedWordIndices.Count >= words.Count)
        {
            usedWordIndices.Clear();
        }
        
        // 选择一个未使用的随机单词
        int index;
        do
        {
            index = Random.Range(0, words.Count);
        }
        while (usedWordIndices.Contains(index) && usedWordIndices.Count < words.Count);
        
        // 记录已使用
        usedWordIndices.Add(index);
        
        // 为这次使用重新生成不完整形式
        Word word = words[index];
        
        // 使用GeneratePartialWord重新生成不完整形式，确保随机性
        if (word.parts != null && word.parts.Count > 1)
        {
            var (incompleteForm, missingPart) = GeneratePartialWord(word);
            word.incomplete = incompleteForm;
            word.answer = missingPart;
        }
        else
        {
            var (incompleteForm, missingPart) = GenerateIncompleteWord(word.english);
            word.incomplete = incompleteForm;
            word.answer = missingPart;
        }
        
        return word;
    }
   
    /// <summary>
    /// 获取单词的音标分段
    /// </summary>
    public List<string> GetPhoneticParts(Word word)
    {
        List<string> resultParts = new List<string>();
        
        // 如果单词已有预处理的音标分段，返回副本
        if (word.phoneticParts != null && word.phoneticParts.Count > 0)
        {
            Debug.Log($"WordDatabase: 单词 '{word.english}' 的音标分段数量: {word.phoneticParts.Count}");
            
            foreach (string part in word.phoneticParts)
            {
                resultParts.Add(part); // 创建副本而不是返回引用
            }
            
            return resultParts;
        }
        
        // 如果没有预处理的音标分段，尝试基于空格拆分
        if (!string.IsNullOrEmpty(word.phonetic))
        {
            Debug.Log($"WordDatabase: 尝试为单词 '{word.english}' 按空格分割音标: '{word.phonetic}'");
            
            string[] parts = word.phonetic.Split(' ');
            foreach (string part in parts)
            {
                if (!string.IsNullOrEmpty(part))
                {
                    resultParts.Add(part);
                }
            }
            
            Debug.Log($"WordDatabase: 按空格分割得到 {resultParts.Count} 个音标部分");
        }
        else
        {
            Debug.LogWarning($"WordDatabase: 单词 '{word.english}' 没有音标信息");
        }
        
        return resultParts;
    }
    
    /// <summary>
    /// 设置单词列表（从Excel导入时使用）
    /// </summary>
    public void SetWordList(List<Word> newWords)
    {
        if (newWords == null || newWords.Count == 0)
        {
            Debug.LogWarning("尝试设置空的单词列表");
            return;
        }
        
        // 备份旧的单词数量以便日志
        int oldCount = words.Count;
        
        // 清空现有单词列表
        words.Clear();
        usedWordIndices.Clear();
        
        // 添加新单词，并为每个单词生成不完整形式
        foreach (Word word in newWords)
        {
            // 为每个单词生成不完整形式
            var (incompleteForm, missingPart) = GeneratePartialWord(word);
            
            // 添加处理后的单词
            Word newWord = word;
            newWord.incomplete = incompleteForm;
            newWord.answer = missingPart;
            
            // 处理音标分段，确保与单词分段对应
            ProcessPhoneticParts(ref newWord);
            
            words.Add(newWord);
        }
        
        Debug.Log($"单词列表已更新：原有 {oldCount} 个单词，现在 {words.Count} 个单词");
    }
    
    /// <summary>
    /// 处理单词的音标分段，确保与单词分段对应
    /// </summary>
    private void ProcessPhoneticParts(ref Word word)
    {
        // 如果没有音标，初始化空的音标分段列表，每个部分对应空字符串
        if (string.IsNullOrEmpty(word.phonetic))
        {
            word.phoneticParts = new List<string>();
            for (int i = 0; i < word.parts.Count; i++)
            {
                word.phoneticParts.Add("");
            }
            return;
        }
        
        // 如果已有音标分段，并且数量与单词分段一致，无需处理
        if (word.phoneticParts != null && word.phoneticParts.Count == word.parts.Count)
        {
            // 检查是否有分段问题（所有音标都在第一个元素中）
            if (word.phoneticParts.Count > 1 && !string.IsNullOrEmpty(word.phoneticParts[0]) && 
                word.phoneticParts[0].Length > word.parts[0].Length * 2)
            {
                Debug.LogWarning($"检测到音标分段问题: 单词 '{word.english}' 的全部音标都在第一个元素中: '{word.phoneticParts[0]}'。尝试重新分段...");
                // 检测到问题，清空现有分段重新处理
                word.phoneticParts.Clear();
            }
            else
            {
                return; // 分段正常，无需处理
            }
        }
        
        // 如果没有音标分段，创建新列表
        if (word.phoneticParts == null)
        {
            word.phoneticParts = new List<string>();
        }
        else
        {
            word.phoneticParts.Clear();
        }
        
        // 首先尝试智能分割音标
        bool success = TrySmartPhoneticSplit(ref word);
        if (success)
        {
            return; // 智能分割成功，直接返回
        }
        
        // 智能分割失败，尝试按空格分割音标
        string[] phoneticParts = word.phonetic.Split(' ');
        
        // 简单情况：音标段数与单词段数相同，直接一一对应
        if (phoneticParts.Length == word.parts.Count)
        {
            for (int i = 0; i < phoneticParts.Length; i++)
            {
                word.phoneticParts.Add(phoneticParts[i]);
            }
            Debug.Log($"按空格分割音标成功: 单词 '{word.english}', 分段数: {word.phoneticParts.Count}");
            return;
        }
        
        // 复杂情况：音标段数与单词段数不同，尝试更智能的匹配
        
        // 如果音标段数少于单词段数，可能有些字母不发音
        if (phoneticParts.Length < word.parts.Count)
        {
            // 先分配已有的音标段
            int phoneticIndex = 0;
            for (int i = 0; i < word.parts.Count; i++)
            {
                if (phoneticIndex < phoneticParts.Length)
                {
                    // 先假设当前单词部分对应当前音标部分
                    word.phoneticParts.Add(phoneticParts[phoneticIndex]);
                    phoneticIndex++;
                }
                else
                {
                    // 音标用完了，剩下的单词部分可能不发音
                    word.phoneticParts.Add("");
                }
            }
        }
        // 如果音标段数多于单词段数，需要合并一些音标段
        else if (phoneticParts.Length > word.parts.Count)
        {
            // 简单处理：前面的音标段一一对应，多余的合并到最后一个
            for (int i = 0; i < word.parts.Count - 1; i++)
            {
                if (i < phoneticParts.Length)
                {
                    word.phoneticParts.Add(phoneticParts[i]);
                }
                else
                {
                    word.phoneticParts.Add("");
                }
            }
            
            // 处理最后一个部分，合并剩余的所有音标段
            StringBuilder lastPhonetic = new StringBuilder();
            for (int i = word.parts.Count - 1; i < phoneticParts.Length; i++)
            {
                if (i > word.parts.Count - 1)
                {
                    lastPhonetic.Append(" ");
                }
                lastPhonetic.Append(phoneticParts[i]);
            }
            word.phoneticParts.Add(lastPhonetic.ToString());
        }
        
        Debug.Log($"处理单词 '{word.english}' 的音标分段: {word.parts.Count} 个单词部分, {word.phoneticParts.Count} 个音标部分");
    }
    
    /// <summary>
    /// 尝试智能分割音标，匹配单词分段
    /// </summary>
    private bool TrySmartPhoneticSplit(ref Word word)
    {
        // 如果音标为空或单词分段为空，无法处理
        if (string.IsNullOrEmpty(word.phonetic) || word.parts == null || word.parts.Count == 0)
        {
            return false;
        }
        
        Debug.Log($"尝试智能分割单词 '{word.english}' 的音标 '{word.phonetic}'");
        
        // 去除音标中的空格，便于处理
        string cleanPhonetic = word.phonetic.Replace(" ", "");
        int phoneticLength = cleanPhonetic.Length;
        
        // 单词总长度
        int wordLength = 0;
        foreach (string part in word.parts)
        {
            wordLength += part.Length;
        }
        
        // 如果音标比单词短很多或长很多，可能不适合按比例分配
        if (phoneticLength < wordLength / 2 || phoneticLength > wordLength * 2)
        {
            Debug.LogWarning($"音标长度({phoneticLength})与单词长度({wordLength})差异太大，不适合按比例分配");
            return false;
        }
        
        // 按单词各部分长度比例分配音标
        word.phoneticParts.Clear();
        int phoneticIndex = 0;
        
        for (int i = 0; i < word.parts.Count; i++)
        {
            string part = word.parts[i];
            int partLength = part.Length;
            
            // 计算应分配的音标长度（按比例）
            float ratio = (float)partLength / wordLength;
            int phoneticPartLength = Mathf.RoundToInt(phoneticLength * ratio);
            
            // 确保至少分配1个字符（如果有）
            if (phoneticPartLength == 0 && phoneticIndex < phoneticLength)
            {
                phoneticPartLength = 1;
            }
            
            // 确保不超出音标总长度
            if (phoneticIndex + phoneticPartLength > phoneticLength)
            {
                phoneticPartLength = phoneticLength - phoneticIndex;
            }
            
            if (phoneticPartLength <= 0 || phoneticIndex >= phoneticLength)
            {
                // 已经没有音标可分配
                word.phoneticParts.Add("");
            }
            else
            {
                // 提取对应部分的音标
                string phoneticPart = cleanPhonetic.Substring(phoneticIndex, phoneticPartLength);
                word.phoneticParts.Add(phoneticPart);
                phoneticIndex += phoneticPartLength;
            }
        }
        
        // 检查是否已处理完所有音标
        if (phoneticIndex < phoneticLength)
        {
            // 有剩余音标，添加到最后一个部分
            if (word.phoneticParts.Count > 0)
            {
                int lastIndex = word.phoneticParts.Count - 1;
                word.phoneticParts[lastIndex] += cleanPhonetic.Substring(phoneticIndex);
            }
        }
        
        Debug.Log($"智能分割音标结果: 单词 '{word.english}'");
        for (int i = 0; i < word.parts.Count; i++)
        {
            Debug.Log($"  段 {i}: 单词='{word.parts[i]}', 音标='{word.phoneticParts[i]}'");
        }
        
        return true;
    }
    
    /// <summary>
    /// 强制重新处理所有单词的音标分段
    /// </summary>
    public void ReprocessAllPhoneticParts()
    {
        Debug.Log($"开始重新处理所有单词的音标分段，单词数量: {words.Count}");
        
        for (int i = 0; i < words.Count; i++)
        {
            Word word = words[i];
            
            // 检查是否有分段问题（所有音标在一个元素中）
            bool needsReprocessing = false;
            
            if (word.phoneticParts == null || word.phoneticParts.Count == 0)
            {
                needsReprocessing = true;
            }
            else if (word.phoneticParts.Count != word.parts.Count)
            {
                needsReprocessing = true;
            }
            else if (word.phoneticParts.Count > 1 && !string.IsNullOrEmpty(word.phonetic) && 
                     !string.IsNullOrEmpty(word.phoneticParts[0]) && 
                     word.phoneticParts[0].Length > word.parts[0].Length * 2)
            {
                // 可能所有音标都在第一个元素中
                needsReprocessing = true;
            }
            
            if (needsReprocessing)
            {
                Debug.Log($"重新处理单词 '{word.english}' 的音标分段");
                ProcessPhoneticParts(ref word);
                words[i] = word; // 更新回列表
            }
        }
        
        Debug.Log("所有单词的音标分段处理完成");
    }
    
    /// <summary>
    /// 根据单词的parts生成不完整形式和答案
    /// </summary>
    /// <param name="word">要处理的单词</param>
    /// <returns>包含不完整形式和答案的元组</returns>
    private (string incomplete, string answer) GeneratePartialWord(Word word)
    {
        // 如果单词没有拆分部分或者只有一部分，使用原始的GenerateIncompleteWord方法
        if (word.parts == null || word.parts.Count <= 1)
        {
            return GenerateIncompleteWord(word.english);
        }
        
        // 随机选择一个部分隐藏
        int partToHide = Random.Range(0, word.parts.Count);
        string missingPart = word.parts[partToHide];
        
        // 构建不完整单词，隐藏选中的部分
        string incompleteWord = "";
        for (int i = 0; i < word.parts.Count; i++)
        {
            if (i == partToHide)
            {
                // 用下划线替换隐藏的部分
                incompleteWord += new string('_', missingPart.Length);
            }
            else
            {
                incompleteWord += word.parts[i];
            }
        }
        
        // 只返回被隐藏的部分作为答案，不附加提示
        return (incompleteWord, missingPart);
    }
} 